<template>
   <div>
       <div v-pos:top="pos" class="box">指令</div>
       <div v-pos:left="pos" class="box">指令2</div>
   </div>
</template>

<script lang='ts'>
import {ref,DirectiveBinding} from 'vue'
export default {
    directives:{
        pos:{
            mounted(el:HTMLElement,binding:DirectiveBinding){
               let diarg=binding.arg   //指令绑定的key
               let divalue=binding.value   //指令的值
               let rect:DOMRect=el.getBoundingClientRect()
               let top=''
               let left=''
               switch(diarg){
                   case 'top':
                     top=(divalue??rect.top) +'px'
                     left=rect.left +'px'
                     break;
                   case 'left':
                     top=rect.top +'px'
                     left=(divalue??rect.left) +'px'
                     break;
               }
               el.style.cssText=`
                  position:absolute;
                  top:${top} ;
                  left:${left};
               `
               el.onmousedown=function(e:MouseEvent){
                    let offsetTop=e.offsetY
                    let offsetLeft=e.offsetX
                    el.onmousemove=function(ex:MouseEvent){
                        let extop=ex.clientY
                        let exleft=ex.clientX
                        el.style.top=extop-offsetTop +'px'
                        el.style.left=exleft-offsetLeft +'px'
                    }
               }
              el.onmouseup=function(){
                  el.onmousemove=null
              }
              el.onmouseout=function(){
                  el.onmousemove=null
              }
            }
        }
    },
    setup(){
       let pos=ref<number>(100)
       return {pos}
    }
}
</script>

<style scoped lang='less'>
.box{
    width:150px;
    height: 50px;
    line-height: 50px;
    text-align: center;
    border: 1px solid #5689fd;
}
</style>